﻿using System;
using System.Linq;
using System.Runtime.Serialization;
using System.ServiceModel;
using System.ServiceModel.Activation;
using System.IO;
using System.Collections.Generic;
using System.Data.SqlClient;
namespace SSCCMembership.Web.Services.Members
{
    [ErrorHandlerBehavior]
    [ServiceContract(Namespace = "")]
    [AspNetCompatibilityRequirements(RequirementsMode = AspNetCompatibilityRequirementsMode.Allowed)]
    public class RefCodesReadOnlyService
    {
        [OperationContract]
        public RefCode[] GetRefCodes(int CodeType)
        {
            using (var Q = new Query(
                "SELECT RC.ID, RC.Description FROM SSCC_REF_ReferenceCode AS RC INNER JOIN SSCC_REF_CodeType AS CT ON RC.CodeType = CT.ID WHERE (CT.ID = @CodeType) ORDER BY RC.Weight",
                new Dictionary<SqlParameter, object>()
                {
                    {new SqlParameter("@CodeType", System.Data.SqlDbType.Int), CodeType}
                }
                ))
            {
                return Q.Select((R) => new RefCode((int)R["ID"], R["Description"].ToString())).ToArray();
            }
        }

        [OperationContract]
        public RefCode[] GetRefCodesL2(int RefCode)
        {
            using (var Q = new Query(
                "SELECT L2.ID, L2.Description FROM SSCC_REF_ReferenceCode AS RC INNER JOIN SSCC_REF_ReferenceCodeL2 AS L2 ON RC.ID = L2.ReferenceCode WHERE (RC.ID = @RefCode) ORDER BY L2.Weight",
                new Dictionary<SqlParameter, object>()
                            {
                                {new SqlParameter("@RefCode", System.Data.SqlDbType.Int), RefCode}
                            }
                ))
            {
                return Q.Select((R) => new RefCode((int)R["ID"], R["Description"].ToString())).ToArray();
            }
        }
    }
    public static class RefCodeExtensions
    {

        private static object LoadRefCodeProperty(int ID, string PropertyName, bool IsL2)
        {
            using (var Q = new Query(
                "SELECT " + PropertyName + " FROM SSCC_REF_ReferenceCode" + (IsL2?"L2":"") + " WHERE (ID = @ID)",
                new Dictionary<SqlParameter, object>()
                {
                    {new SqlParameter("@ID", System.Data.SqlDbType.Int), ID}
                }
                ))
            {
                return Q.First()[PropertyName];
            }
        }
        public static string GetRefCodeDescription(this int ID)
        {
            return LoadRefCodeProperty(ID, "Description", false).ToString();
            //DataModel DataContext = new DataModel();
            //return DataContext.SSCC_REF_ReferenceCode.Where((RC) => RC.ID == ID).First().Description;
        }
        public static string GetRefCodeDescription(this int? ID)
        {
            if (!ID.HasValue)
            {
                return null;
            }
            else
            {
                return LoadRefCodeProperty(ID.Value, "Description", false).ToString();
                //DataModel DataContext = new DataModel();
                //return DataContext.SSCC_REF_ReferenceCode.Where((RC) => RC.ID == ID).First().Description;
            }
        }

        public static T GetRefCodeMetadata<T>(this int ID)
        {
            try
            {
                //DataModel DataContext = new DataModel();
                //var MetaData = DataContext.SSCC_REF_ReferenceCode.Where((RC) => RC.ID == ID).First().MetaData;
                var MetaData = (byte[])LoadRefCodeProperty(ID, "MetaData", false);
                MemoryStream MS = new MemoryStream(MetaData);
                DataContractSerializer S = new DataContractSerializer(typeof(T));
                return (T)S.ReadObject(MS);
            }
            catch
            {
                return default(T);
            }

            //return DataContext.SSCC_REF_ReferenceCode.Where((RC) => RC.ID == ID).First().Description;
        }
        public static T GetRefCodeMetadata<T>(this int? ID)
        {
            try
            {
                if (ID == null)
                {
                    return default(T);
                }
                else
                {
                    //DataModel DataContext = new DataModel();
                    //var MetaData = DataContext.SSCC_REF_ReferenceCode.Where((RC) => RC.ID == ID).First().MetaData;
                    var MetaData = (byte[])LoadRefCodeProperty(ID.Value, "MetaData", false);

                    MemoryStream MS = new MemoryStream(MetaData);
                    DataContractSerializer S = new DataContractSerializer(typeof(T));
                    return (T)S.ReadObject(MS);
                }
            }
            catch
            {
                return default(T);
            }

        }

        public static int GetRefCodeWeight(this int ID)
        {
            try
            {
                return (int)LoadRefCodeProperty(ID, "Weight", false);
                //DataModel DataContext = new DataModel();
                //return DataContext.SSCC_REF_ReferenceCode.Where((RC) => RC.ID == ID).First().Weight;
            }
            catch (Exception)
            {
                return default(int);
            }

        }
        public static int GetRefCodeWeight(this int? ID)
        {
            try
            {
                if (ID == null)
                {
                    return default(int);
                }
                else
                {
                    return (int)LoadRefCodeProperty(ID.Value, "Weight", false);
                    //DataModel DataContext = new DataModel();
                    //return DataContext.SSCC_REF_ReferenceCode.Where((RC) => RC.ID == ID).First().Weight;
                }
            }
            catch
            {
                return default(int);
            }
        }

        public static int GetRefCodeCodeType(this int ID)
        {
            return (int)LoadRefCodeProperty(ID, "CodeType", false);
            //DataModel DataContext = new DataModel();
            //return DataContext.SSCC_REF_ReferenceCode.Where((RC) => RC.ID == ID).Select((RC) => RC.SSCC_REF_CodeType.ID).First();
        }
        public static int? GetRefCodeCodeType(this int? ID)
        {
            try
            {
                if (ID == null)
                {
                    return null;
                }
                else
                {
                    return (int)LoadRefCodeProperty(ID.Value, "CodeType", false);
                    //DataModel DataContext = new DataModel();
                    //return DataContext.SSCC_REF_ReferenceCode.Where((RC) => RC.ID == ID).Select((RC) => RC.SSCC_REF_CodeType.ID).First();
                }
            }
            catch
            {
                return null;
            }

        }


        public static string GetRefCodeShortName(this int ID)
        {
            return LoadRefCodeProperty(ID, "ShortName", false).ToString();
            //DataModel DataContext = new DataModel();
            //return DataContext.SSCC_REF_ReferenceCode.Where((RC) => RC.ID == ID).First().ShortName;
        }
        public static string GetRefCodeShortName(this int? ID)
        {
            if (ID == null)
            {
                return null;
            }
            else
            {
                return LoadRefCodeProperty(ID.Value, "ShortName", false).ToString();
                //DataModel DataContext = new DataModel();
                //return DataContext.SSCC_REF_ReferenceCode.Where((RC) => RC.ID == ID).First().ShortName;
            }
        }
    }

    [DataContract]
    public class RefCode
    {
        public RefCode(int ID, string Description)
        {
            this.ID = ID;
            this.Name = Description;
        }
        [DataMember]
        public int ID { get; set; }
        [DataMember]
        public string Name { get; set; }
    }
}
